﻿using FI.BatchJob.Web.Data;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using System;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;

namespace FI.BatchJob.Web.Extensions
{

    internal class HostClearHistoryService : IHostedService, IDisposable
    {
        private static object lockObj = new object();//定义锁

        private readonly IServiceScopeFactory scopeFactory;

        private readonly ILogger _logger;
        private ApplicationDbContext _context;
        private Timer _timer;
        private readonly IWebHostEnvironment _hostingEnv;

        public HostClearHistoryService(IServiceScopeFactory scopeFactory,
            ILogger<HostClearHistoryService> logger, IWebHostEnvironment hostingEnv)
        {
            this.scopeFactory = scopeFactory;
            _logger = logger;
            _hostingEnv = hostingEnv;
        }

        public Task StartAsync(CancellationToken cancellationToken)
        {
            _logger.LogInformation("Clear history Background Service is starting.");

            _timer = new Timer(DoWork, null, TimeSpan.Zero, TimeSpan.FromHours(2));//TimeSpan.FromSeconds(5));//

            return Task.CompletedTask;
        }

        private void DoWork(object state)
        {
            _logger.LogInformation(string.Format("[{0:yyyy-MM-dd hh:mm:ss}]Clear history Background Service is working.", DateTime.Now));

            lock (lockObj)
            {
                using (var scope = scopeFactory.CreateScope())
                {
                    _context = scope.ServiceProvider.GetRequiredService<ApplicationDbContext>();

                    #region //process history
                    try
                    {
                        var keys = _context.ScheduleHistories.GroupBy(n => new { n.JobGroup, n.JobName }).Select(n => n.Key).ToList();

                        foreach (var key in keys)
                        {

                            var count = _context.ScheduleHistories.Where(n => n.JobName == key.JobName && n.JobGroup == key.JobGroup).Count();

                            if (count > 200)
                            {
                                var deleteHistories = _context.ScheduleHistories.OrderBy(n => n.ID).Take(100).ToList();

                                foreach (var item in deleteHistories)
                                {
                                    _context.Remove(item);
                                }
                            }
                        }
                        _context.SaveChanges();

                    }
                    catch (Exception ex)
                    {
                        _logger.LogError(ex.Message, ex.ToString());

                    }
                    #endregion

                }
            }
        }

        public Task StopAsync(CancellationToken cancellationToken)
        {
            _logger.LogInformation("Clear history Background Service is stopping.");

            _timer?.Change(Timeout.Infinite, 0);

            return Task.CompletedTask;
        }

        public void Dispose()
        {
            _timer?.Dispose();
        }
    }




}
